ARIA: `tab`-Rolle
Die ARIA tab
-Rolle zeigt ein interaktives Element innerhalb einer tablist
an, das beim Aktivieren sein zugehöriges tabpanel
anzeigt.
<button role="tab" aria-selected="true" aria-controls="tabpanel-id" id="tab-id">
Tab label
</button>
Beschreibung
Ein Element mit der tab
-Rolle steuert die Sichtbarkeit eines zugeordneten Elements mit der Rolle tabpanel
. Das übliche Benutzererlebnismuster ist eine Gruppe von visuellen Registerkarten oberhalb oder seitlich eines Inhaltsbereichs, und die Auswahl einer anderen Registerkarte ändert den Inhalt und macht die ausgewählte Registerkarte auffälliger als die anderen.
Elemente mit der Rolle tab
müssen entweder ein untergeordnetes Element eines Elements mit der tablist
-Rolle sein oder ihre id
als Teil der aria-owns
-Eigenschaft einer tablist
haben. Diese Kombination zeigt unterstützender Technologie, dass das Element Teil einer Gruppe verwandter Elemente ist. Einige unterstützende Technologien geben die Anzahl der Elemente mit der tab
-Rolle innerhalb einer tablist
an und informieren die Benutzer darüber, welches tab
sie derzeit anvisiert haben. Weiterhin sollte ein Element mit der tab
-Rolle die aria-controls
-Eigenschaft enthalten, die ein entsprechendes tabpanel
(das eine tabpanel
-Rolle hat) durch die id
dieses Elements identifiziert. Wenn ein Element mit der tabpanel
-Rolle den Fokus hat oder ein untergeordnetes Element davon den Fokus hat, zeigt das an, dass das verbundene Element mit der tab
-Rolle die aktive Registerkarte in einer tablist
ist.
Wenn Elemente mit der tab
-Rolle ausgewählt oder aktiv sind, sollten sie ihr aria-selected
-Attribut auf true
setzen. Andernfalls sollte ihr aria-selected
-Attribut auf false
gesetzt werden. Wenn eine einfach auswählbare tablist
ausgewählt oder aktiv ist, sollte das hidden
-Attribut der anderen Tabellenelemente auf true
gesetzt werden, bis der Benutzer die mit dieser Tabelle verbundene Registerkarte auswählt. Wenn eine mehrfach auswählbare tablist
ausgewählt oder aktiv ist, sollte ihr entsprechendes gesteuertes tabpanel
sein aria-expanded
-Attribut auf true
und sein hidden
-Attribut auf false
gesetzt haben, ansonsten umgekehrt.
Alle Nachfahren sind präsentational
Es gibt einige Arten von Benutzeroberflächenkomponenten, die, wenn sie in einer Plattform-Zugänglichkeits-API repräsentiert werden, nur Text enthalten können. Zugänglichkeits-APIs haben keine Möglichkeit, semantische Elemente in einem tab
darzustellen. Um mit dieser Einschränkung umzugehen, wenden Browser automatisch die Rolle presentation
auf alle nachfolgenden Elemente eines beliebigen tab
-Elements an, da es eine Rolle ist, die keine semantischen Kinder unterstützt.
Zum Beispiel betrachten Sie das folgende tab
-Element, das eine Überschrift enthält.
<div role="tab"><h3>Title of my tab</h3></div>
Da Nachfahren von tab
präsentational sind, ist der folgende Code äquivalent:
<div role="tab"><h3 role="presentation">Title of my tab</h3></div>
Aus der Perspektive des Benutzers unterstützender Technologien existiert die Überschrift nicht, da die vorherigen Codeschnipsel im Zugänglichkeitsbaum dem folgenden gleichwertig sind:
<div role="tab">Title of my tab</div>
Zugehörige Rollen und Attribute
aria-selected
-
boolean
aria-controls
-
id
des Elements mit dertabpanel
-Rolle - id
-
Inhalt
Tastaturinteraktionen
Taste | Aktion |
---|---|
Tab | Wenn der Fokus außerhalb der tablist ist, wird der Fokus auf die aktive Registerkarte verschoben. Wenn der Fokus auf der aktiven Registerkarte ist, wird der Fokus auf das nächste Element in der Tastaturfokusreihenfolge verschoben, idealerweise auf das zugehörige tabpanel der aktiven Registerkarte. |
→ | Fokussiert und aktiviert optional die nächste Registerkarte in der Registerkartenliste. Wenn die aktuelle Registerkarte die letzte in der Registerkartenliste ist, wird die erste Registerkarte aktiviert. |
← | Fokussiert und aktiviert optional die vorherige Registerkarte in der Registerkartenliste. Wenn die aktuelle Registerkarte die erste in der Registerkartenliste ist, wird die letzte Registerkarte aktiviert. |
Delete | Entfernt, wenn erlaubt, die aktuell ausgewählte Registerkarte aus der Registerkartenliste. |
Erforderliche JavaScript-Funktionen
Hinweis: Obwohl es Möglichkeiten gibt, tab-ähnliche Funktionalität ohne JavaScript zu erstellen, gibt es keine Ersatzkombination, die nur HTML und CSS verwendet, die den oben erforderlichen Funktionsumfang für zugängliche Registerkarten mit Inhalt bietet.
Beispiel
Dieses Beispiel kombiniert die Rolle tab
mit tablist
und Elementen mit tabpanel
, um eine interaktive Gruppe von Registerkarteninhalten zu erstellen. Hier umschließen wir unsere Gruppe von Inhalten in einem div
, wobei unsere tablist
ein aria-label
hat, das es für unterstützende Technologien kennzeichnet. Jede tab
ist ein button
mit den zuvor erwähnten Attributen. Die erste tab
hat sowohl tabindex="0"
als auch aria-selected="true"
angewendet. Diese beiden Attribute müssen immer so koordiniert werden – wenn eine andere Registerkarte ausgewählt wird, hat sie dann tabindex="0"
und aria-selected="true"
angewendet. Alle nicht ausgewählten Registerkarten müssen aria-selected="false"
und tabindex="-1"
haben.
Alle tabpanel
-Elemente haben tabindex="0"
, um sie tab-bar zu machen, und alle außer dem derzeit aktiven haben das hidden
-Attribut. Das hidden
-Attribut wird entfernt, wenn ein tabpanel
mit JavaScript sichtbar wird. Es gibt einen einfachen Styling, der die Buttons umgestaltet und den z-index
der tab
-Elemente ändert, um die Illusion zu erzeugen, dass es mit dem tabpanel
für aktive Elemente verbunden ist, und die Illusion, dass inaktive Elemente hinter dem aktiven tabpanel
liegen.
<div class="tabs">
<div role="tablist" aria-label="Sample Tabs">
<button
role="tab"
aria-selected="true"
aria-controls="panel-1"
id="tab-1"
tabindex="0">
First Tab
</button>
<button
role="tab"
aria-selected="false"
aria-controls="panel-2"
id="tab-2"
tabindex="-1">
Second Tab
</button>
<button
role="tab"
aria-selected="false"
aria-controls="panel-3"
id="tab-3"
tabindex="-1">
Third Tab
</button>
</div>
<div id="panel-1" role="tabpanel" tabindex="0" aria-labelledby="tab-1">
<p>Content for the first panel</p>
</div>
<div id="panel-2" role="tabpanel" tabindex="0" aria-labelledby="tab-2" hidden>
<p>Content for the second panel</p>
</div>
<div id="panel-3" role="tabpanel" tabindex="0" aria-labelledby="tab-3" hidden>
<p>Content for the third panel</p>
</div>
</div>
Es gibt zwei Dinge, die wir mit JavaScript tun müssen: Wir müssen den Fokus und die Tab-Index unserer tab
-Elemente mit den rechten und linken Pfeilen ändern und wir müssen die aktive tab
und tabpanel
ändern, wenn wir auf eine tab
klicken.
Um das erste zu erreichen, hören wir auf das keydown
-Ereignis auf der tablist
. Wenn die key
des Ereignisses ArrowRight
oder ArrowLeft
ist, reagieren wir auf das Ereignis. Wir beginnen damit, den tabindex
des aktuellen tab
-Elements auf -1 zu setzen, was es nicht mehr tab-bar macht. Dann, wenn der rechte Pfeil gedrückt wird, erhöhen wir unseren Tab-Fokuszähler um eins. Wenn der Zähler größer als die Anzahl der tab
-Elemente ist, die wir haben, gehen wir zurück zur ersten Registerkarte, indem wir diesen Zähler auf 0 setzen. Wenn der linke Pfeil gedrückt wird, verringern wir unseren Tab-Fokuszähler um eins, und wenn es dann kleiner als 0 ist, setzen wir es auf die Anzahl der tab
-Elemente minus eins (um zum letzten Element zu gelangen). Schließlich setzen wir den focus
auf das tab
-Element, dessen Index dem Tab-Fokuszähler entspricht, und setzen seinen tabindex
auf 0, um es tab-bar zu machen.
Um die aktive tab
und tabpanel
zu ändern, haben wir eine Funktion, die das Ereignis übernimmt, das Element, das das Ereignis ausgelöst hat, das übergeordnete Element des Auslöselements und dessen übergeordnetes Element erhält. Wir finden dann alle Registerkarten mit aria-selected="true"
im übergeordneten Element und setzen es auf false
, dann setzen wir das aria-selected
des Auslöselements auf true
. Danach finden wir alle tabpanel
-Elemente im Großelternelement, machen sie alle hidden
und wählen schließlich das Element aus, dessen id
gleich dem aria-controls
des auslösenden tab
ist, und entfernen das hidden
-Attribut, um es sichtbar zu machen.
window.addEventListener("DOMContentLoaded", () => {
// Only handle one particular tablist; if you have multiple tab
// lists (might even be nested), you have to apply this code for each one
const tabList = document.querySelector('[role="tablist"]');
const tabs = tabList.querySelectorAll(':scope > [role="tab"]');
// Add a click event handler to each tab
tabs.forEach((tab) => {
tab.addEventListener("click", changeTabs);
});
// Enable arrow navigation between tabs in the tab list
let tabFocus = 0;
tabList.addEventListener("keydown", (e) => {
// Move right
if (e.key === "ArrowRight" || e.key === "ArrowLeft") {
tabs[tabFocus].setAttribute("tabindex", -1);
if (e.key === "ArrowRight") {
tabFocus++;
// If we're at the end, go to the start
if (tabFocus >= tabs.length) {
tabFocus = 0;
}
// Move left
} else if (e.key === "ArrowLeft") {
tabFocus--;
// If we're at the start, move to the end
if (tabFocus < 0) {
tabFocus = tabs.length - 1;
}
}
tabs[tabFocus].setAttribute("tabindex", 0);
tabs[tabFocus].focus();
}
});
});
function changeTabs(e) {
const targetTab = e.target;
const tabList = targetTab.parentNode;
const tabGroup = tabList.parentNode;
// Remove all current selected tabs
tabList
.querySelectorAll(':scope > [aria-selected="true"]')
.forEach((t) => t.setAttribute("aria-selected", false));
// Set this tab as selected
targetTab.setAttribute("aria-selected", true);
// Hide all tab panels
tabGroup
.querySelectorAll(':scope > [role="tabpanel"]')
.forEach((p) => p.setAttribute("hidden", true));
// Show the selected panel
tabGroup
.querySelector(`#${targetTab.getAttribute("aria-controls")}`)
.removeAttribute("hidden");
}
Beste Praktiken
Es wird empfohlen, ein <button>
-Element mit der tab
-Rolle zu verwenden, da diese eingebaute funktionale und zugängliche Funktionen bieten, anstatt sie selbst hinzufügen zu müssen. Um die Tabulatortastenfunktionalität für Elemente mit der tab
-Rolle zu steuern, wird empfohlen, alle nicht aktiven Elemente auf tabindex="-1"
zu setzen und das aktive Element auf tabindex="0"
.
Prioritätsreihenfolge
Welche sind die verwandten Eigenschaften und in welcher Reihenfolge wird dieses Attribut oder diese Eigenschaft gelesen, welche Eigenschaft wird Vorrang vor dieser haben und welche Eigenschaft wird überschrieben.
Spezifikationen
Specification |
---|
Accessible Rich Internet Applications (WAI-ARIA) # tab |
Unknown specification |
Siehe auch
- HTML
<button>
-Element - KeyboardEvent.key
- ARIA
tabpanel
-Rolle